var esClient = require("../util/es.js");
var db = require("../util/DataBase.js")

function genESKeyword(articleId, success, error) {

  db.query("SELECT `title`, `content`, `rank` FROM article WHERE `id` = ?", [
    articleId
  ], function (err, results) {
    if(err) {
      error && error("为文章生成keywrod时获取文章失败")
    } else {
      var keyWord = "";
      var content = JSON.parse(results[0].content);
      for(var i = 0, l = content.length; i < l; ++ i) {
        var section = content[i].value;
        switch(section.type) {
          case "text":
            keyWord += section.value;
          break;
        }
      }

      success && success(results[0].title, keyWord, results[0].rank);

    }
  });

}

var searchService = {
  recommend(kw, top, success, error) {

    esClient.search({
      index: 'recommend',
      type: "article",
      body: {
        size: top,
        sort: [
          "_score",
          {
            rank: {
              order: "desc"
            }
          }
        ],
        query: {
          multi_match: {
            query: kw,
            fuzziness: "AUTO",
            fields: [
              "title",
              "keyword",
              "replyList.content"
            ]
          }
        }
      }
    }, (err, result) => {
      if(err) {
        success([]);
      } else {
        var idList = [];
        result.body.hits.hits.forEach((article) => {
          idList.push(article._id);
        })

        if(idList.length == 0) {
          success([]);
          return;
        }

        db.query(
          "SELECT article.id as id, article.title as title, article.knowledge as knowledge, article.content as content, article.question as question, article.user_id as user_id, article.create_datetime as create_datetime, article.rank as `rank` " +
          "FROM article " +
          "WHERE `id` IN (" + idList.join(",") + ") order by field(id, " + idList.join(",") + ")",
          [],
          function (err, results) {
            if(idList.length > results.length) {
              //es中存在幽灵数据
              for(var i = 0, l = idList.length; i < l; ++ i) {
                var esId = idList[i];
                if(!results.some((dbResult) => {
                  return dbResult.id == esId;
                })) {
                  //删除幽灵数据
                  esClient.delete({
                    index: 'recommend',
                    type: 'article',
                    id: esId
                  });
                }
              }
            }

            if(err) {
              error && error("搜索查询帖子失败");
            } else {

              if(results.length <= 0) {
                success([]);
                return;
              }

              let loaded = 0;
              let len = results.length;

              results.forEach((result) => {

                (function (_result) {

                  db.query("SELECT `id`, `nickname`, `avatar_url` FROM `user` WHERE `id` = ?", [_result.user_id], function (err, userResults) {

                    if(err) {
                      error && error("获取作者信息失败");
                      return;
                    }

                    _result.user = userResults[0];

                    if(_result.hasOwnProperty("reply_user_id"))
                    {

                      db.query("SELECT `id`, `nickname`, `avatar_url` FROM `user` WHERE `id` = ?", [_result.reply_user_id], function (err, userResults) {

                        if(err) {
                          error && error("获取评论作者信息失败");
                          return;
                        }

                        _result.reply_user = userResults[0];

                        if( ++ loaded >= len ) {
                          success(results);
                        }

                      });

                    }
                    else {

                      if( ++ loaded >= len ) {
                        success(results);
                      }

                    }

                  });

                })(result);

              });

            }
          }
        );

      }
    });

  },
  addArticle(articleId, success, error) {

    genESKeyword(articleId, function (title, keyword, rank) {

      esClient.index({
        index: 'recommend',
        type: 'article',
        id: articleId,
        body: {
          title: title,
          keyword: keyword,
          rank: rank + 0.1,
          replyList: []
        }
      }, (err, result) => {
        if(err) {
          error && error(err)
        } else {
          success && success(result);
        }
      });

    }, function (e) {
      error && error(e);
    })



  },
  getArticle(articleId, success, error) {

    esClient.search({
      index: "recommend",
      type: 'article',
      body: {
        query: {
          match: {
            "_id": articleId
          }
        }
      }
    }, (err, result) => {
      if(err) {
        error(err);
      } else {
        success(result);
      }
    });

  },
  updateArticle(articleId, source, params, success, error) {
    esClient.update({
      index: "recommend",
      type: "article",
      id: articleId,
      body: {
        script: {
          source: source,
          lang: "painless",
          params : params
        }
      }
    },
    (err, result) => {
      if(err) {
        error && error(err);
      } else {
        success && success(result);
      }
    })

  },
  updateRank(articleId, inc, success, error) {

    searchService.getArticle(articleId, function (result) {

      if(result.body.hits.hits.length > 0) {

        searchService.updateArticle(
          articleId,
          "ctx._source.rank += params.inc",
          {
            inc: inc
          },
          function (err) {
            success && success();
          },
          function (err) {
            error && error(err);
        })

      } else {
        error && error();
      }

    }, function (err) {
      error && error(err);
    })

  },
  addReply(articleId, reply, success, error) {

    searchService.updateArticle(
      articleId,
      "ctx._source.replyList.add(params.reply)",
      {
        reply: {
          content: reply.content,
          id: reply.id
        }
      },
      function () {
        success && success();
      },
      function (err) {
        error && error(err);
      }
    )

  }
}

module.exports = searchService;

/*var db = require("../util/DataBase.js");

function mergeRecommendArticleAndReply(articleList, replyList, top) {

  var resultList = [];

  resultList = articleList.concat(replyList);

  var articleMap = {};

  for(var i = resultList.length - 1; i >= 0; --i) {

    var result = resultList[i];

    if(articleMap.hasOwnProperty(result.id)) {

      var firedResult = articleMap[result.id];

      firedResult = Object.assign(firedResult, result);
      resultList.splice(i, 1);

    } else {

      articleMap[result.id] = result;

    }

  }
  return resultList.sort(function (a, b) {
    return b.rank - a.rank;
  }).slice(0, top);

}

var searchService = {
  recommend(kw, top, success, error) {

    var kwSplited = kw.split(" ");
    var aritlceLikeSql = [];
    var replyLikeSql = [];
    var articleLikeValues = [];
    var replyLikeValues = [];

    kwSplited.forEach((kwPart) => {
      aritlceLikeSql.push("( `keyword` LIKE ? OR `title` LIKE ? )");
      articleLikeValues.push("%" + kwPart + "%");
      articleLikeValues.push("%" + kwPart + "%");
      replyLikeSql.push("reply.content LIKE ?");
      replyLikeValues.push("%" + kwPart + "%");
    });

    aritlceLikeSql = aritlceLikeSql.join(" OR ");
    replyLikeSql = replyLikeSql.join(" OR ");

    db.query(
      "SELECT article.id as id, article.title as title, article.content as content, article.question as question, article.user_id as user_id, article.create_datetime as create_datetime, article.rank as `rank` " +
      "FROM article " +
      "WHERE " + aritlceLikeSql + " ORDER BY `rank` DESC LIMIT 0,?",
      articleLikeValues.concat(top * 1),
      function (err, articleResults) {
        if(err) {
          error && error("查询推荐帖子失败");
        } else {

          //recommend reply
          db.query(
            "SELECT article.id as id, article.title as title, article.content as content, article.question as question, article.user_id as user_id, article.create_datetime as create_datetime, article.rank as `rank` " +
            "FROM article, reply " +
            "WHERE " + replyLikeSql + " AND article.id = reply.article_id GROUP BY article.id ORDER BY `rank` DESC LIMIT 0,?",
            replyLikeValues.concat(top * 1),
            function (err, replyResults) {
              if(err) {
                error && error("查询推荐评论失败");
              } else {
                var results = mergeRecommendArticleAndReply(articleResults, replyResults, top);

                if(results.length <= 0) {
                  success([]);
                  return;
                }

                let loaded = 0;
                let len = results.length;

                results.forEach((result) => {

                  (function (_result) {

                    db.query("SELECT `id`, `nickname`, `avatar_url` FROM `user` WHERE `id` = ?", [_result.user_id], function (err, userResults) {

                      if(err) {
                        error && error("获取作者信息失败");
                        return;
                      }

                      _result.user = userResults[0];

                      if(_result.hasOwnProperty("reply_user_id"))
                      {

                        db.query("SELECT `id`, `nickname`, `avatar_url` FROM `user` WHERE `id` = ?", [_result.reply_user_id], function (err, userResults) {

                          if(err) {
                            error && error("获取评论作者信息失败");
                            return;
                          }

                          _result.reply_user = userResults[0];

                          if( ++ loaded >= len ) {
                            success(results);
                          }

                        });

                      }
                      else {

                        if( ++ loaded >= len ) {
                          success(results);
                        }

                      }

                    });

                  })(result);

                });

              }
            }
          );

        }
      }
    );

  }
}

module.exports = searchService;*/
